package com.anxin.service.impl;

import java.util.Random;
import java.util.concurrent.TimeUnit;

import org.apache.commons.lang.RandomStringUtils;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;

import com.anxin.constants.RedisKeyGenerator;
import com.anxin.service.IImgCaptchaRemoteService;

@Service
public class ImgCaptchaRemoteServiceImpl implements IImgCaptchaRemoteService {

	private static final Random RANDOM = new Random();

	private static final int DEFAULT_CAPTCHA_EXPIRED_SECONDS = 30 * 60;

	@Autowired
	private RedisTemplate<String, String> stringRedisTemplate;

	@Override
	public String genCaptcha(String token, int codeNum, int captchaExpiredSeconds) {

		String code = RandomStringUtils.random(codeNum, "ABCDEFGHJKLMNPQRSTUVWXYZ23456789");

		String key = RedisKeyGenerator.genImgCaptchaKey(token);
		stringRedisTemplate.opsForValue().set(key, code);
		if (captchaExpiredSeconds <= 0) {
			captchaExpiredSeconds = DEFAULT_CAPTCHA_EXPIRED_SECONDS;
		}
		stringRedisTemplate.expire(key, captchaExpiredSeconds, TimeUnit.SECONDS);

		return code;
	}

	@Override
	public boolean checkAndRemoveCaptcha(String token, String captcha) {
		boolean isValid = isValidCaptcha(token, captcha);
		if (isValid) {
			stringRedisTemplate.delete(RedisKeyGenerator.genImgCaptchaKey(token));
		}
		return isValid;
	}

	@Override
	public boolean isValidCaptcha(String token, String captcha) {
		String key = RedisKeyGenerator.genImgCaptchaKey(token);
		String value = stringRedisTemplate.opsForValue().get(key);
		return StringUtils.endsWithIgnoreCase(captcha, value);
	}

	@Override
	public String takeCaptcha(String token) {
		String key = RedisKeyGenerator.genImgCaptchaKey(token);
		return stringRedisTemplate.opsForValue().get(key);
	}

	@Override
	public boolean canGenCaptcha(String token) {
		String intervalKey = RedisKeyGenerator.genImgCaptchaKey(token);
		return !stringRedisTemplate.hasKey(intervalKey);
	}

	private String generateCode(int length, boolean hex) {
		if (length < 1 || hex && length > 7 || !hex && length > 9)
			return "";
		int base, min, max;
		if (hex) {
			base = 0x10;
		} else {
			base = 10;
		}
		min = new Double(Math.pow(base, length - 1)).intValue();
		max = min * base - 1;
		// System.out.println(length+":\t"+hex+":\t"+max+"\t"+min);
		int result = RANDOM.nextInt(max - min) + min;

		if (hex) {
			return Integer.toHexString(result).toUpperCase();
		} else {
			return Integer.toString(result);
		}
	}
}
